import * as Cesium from "cesium";
import ConeGlowBottomCircleMaterialProperty from './MaterialProperty';
import SimpleLabel from './Bubble/simpleLabel'
// 光锥
export const coneWithLight = (viewer, options) => {
    const position = Cesium.defaultValue(options.position, Cesium.Cartesian3.ZERO);
    const height = Cesium.defaultValue(options.height, 700);
    const bottomRadius = Cesium.defaultValue(options.bottomRadius, 100);
    const color = Cesium.defaultValue(options.color, Cesium.Color.AQUA);
    const modelMatrix = Cesium.Matrix4.multiplyByTranslation(
        Cesium.Transforms.eastNorthUpToFixedFrame(position),
        new Cesium.Cartesian3(0.0, 0.0, height * 0.5), new Cesium.Matrix4()
    );

    const cylinderGeometry = new Cesium.CylinderGeometry({
        length: height,
        topRadius: 0.0,
        bottomRadius: bottomRadius * 0.7,
        vertexFormat: Cesium.MaterialAppearance.MaterialSupport.TEXTURED.vertexFormat
    });

    const cone = new Cesium.GeometryInstance({
        geometry: cylinderGeometry,
        modelMatrix: modelMatrix,
    });

    return viewer.scene.primitives.add(new Cesium.Primitive({
        geometryInstances: [cone],
        appearance: new Cesium.MaterialAppearance({
            material: new Cesium.Material({
                fabric: {
                    type: 'VtxfShader1',
                    uniforms: {
                        color: color
                    },
                    source: /*glsl*/`
                            uniform vec4 color;   
                            czm_material czm_getMaterial(czm_materialInput materialInput)
                            {
                                czm_material material = czm_getDefaultMaterial(materialInput);
                                vec2 st = materialInput.st;
                                float time=fract(czm_frameNumber/10.0);
                                float isAlpha=step(0.5,time);
                                float dis = distance(st, vec2(0.5)); 
                                material.diffuse =1.9 * color.rgb;
                                if(isAlpha>=1.0){
                                    material.alpha = color.a * dis *2.0;
                                }else{
                                    material.alpha = color.a * dis *1.5;
                                }

                                return material;
                            }
                        `
                },
                translucent: false
            }),
            faceForward: false, // 当绘制的三角面片法向不能朝向视点时，自动翻转法向，从而避免法向计算后发黑等问题
            closed: true // 是否为封闭体，实际上执行的是是否进行背面裁剪
        })
    }));
}

// 站点底部圆环
export const bottomCircle = (viewer, options) => {
    const position = Cesium.defaultValue(options.position, Cesium.Cartesian3.ZERO);
    const color = Cesium.defaultValue(options.color, Cesium.Color.AQUA);
    const bottomRadius = Cesium.defaultValue(options.bottomRadius, 100);
    return viewer.entities.add({
        position: position,
        ellipse: {
            semiMinorAxis: bottomRadius * 2,
            semiMajorAxis: bottomRadius * 2,
            height: 0.0,
            material: new ConeGlowBottomCircleMaterialProperty(color),
        }
    });
}

// 渲染站点  传入颜色十六进制字符串，名称，位置{lng,lat,height}
const stations = []
export const renderStation = (viewer, options) => {
    const position = Cesium.defaultValue(options.positions, {
        lng: 0,
        lat: 0
    });
    const positionCar3 = Cesium.Cartesian3.fromDegrees(position.lng, position.lat);
    const conePrimitve = coneWithLight(viewer, {
        position: positionCar3,
        height: 700,
        bottomRadius: 100,
        color: Cesium.Color.fromCssColorString(options.color)
    })

    const bottomCircleEntity = bottomCircle(viewer, {
        position: positionCar3,
        bottomRadius: 100,
        color: Cesium.Color.fromCssColorString(options.color)
    })
    const target = {
        conePrimitve,
        bottomCircleEntity,
        name: options.name
    }
    stations.push(target)
    return target
}

// 删除单个站点，直接删除，而不是隐藏
export const removeStationByName = (viewer, name) => {
    const target = stations.find(item => item.name === name)
    if (target) {
        const { conePrimitve, bottomCircleEntity } = target
        viewer.scene.primitives.remove(conePrimitve)
        viewer.entities.remove(bottomCircleEntity)
        stations.splice(stations.indexOf(target), 1)
    }
}

// 删除所有站点
export const removeAllStations = (viewer) => {
    stations.forEach(item => {
        const { conePrimitve, bottomCircleEntity } = item
        viewer.scene.primitives.remove(conePrimitve)
        viewer.entities.remove(bottomCircleEntity)
    })
    stations.length = 0
}

// 通过名称Array控制站点显示隐藏
export const hideStationByName = (names, isShow) => {
    const targets = stations.filter(item => names.indexOf(item.name) > -1)
    if (targets.length) {
        targets.forEach(target => {
            const { conePrimitve, bottomCircleEntity } = target
            conePrimitve.show = isShow
            bottomCircleEntity.show = isShow
        })
    }
}

// 创建地铁线路 positions:[{lng,lat,height}]
// color:十六进制颜色字符串
// name:线路名称
const lines = []
export const renderLines = (viewer, options) => {
    const positions = Cesium.defaultValue(options.positions, [{
        lng: 0,
        lat: 0
    }]);
    const color = Cesium.defaultValue(options.color, Cesium.Color.AQUA);
    const name = Cesium.defaultValue(options.name, 'line');
    const positionRes = Cesium.Cartesian3.fromDegreesArray(positions);
    const lineEnt = viewer.entities.add({
        name,
        polyline: {
            positions: positionRes,
            width: 20,
            //使用cesium默认的泛光线
            material: new Cesium.PolylineGlowMaterialProperty({
                color: color,
                glowPower: 0.12,
            }),
        }
    });
    lines.push(lineEnt)
    return lineEnt
}

// 删除地铁线路，不是隐藏
export const removeAllLines = (viewer) => {
    lines.forEach(line => {
        line && viewer.entities.remove(line)
    })
}

// 通过名称控制线路显示隐藏
export const hideLineByName = (names, isShow) => {
    lines.forEach(line => {
        if (names.indexOf(line.name) > -1) {
            line.show = isShow
        }
    })
}

// 渲染全部
export const renderAll = (viewer, dataSource) => {
    // console.log(dataSource);
    // 渲染道路
    if (dataSource.length) {
        dataSource.forEach(item => {
            const { paths, name, color, stationsList } = item
            const position = []
            paths.forEach(path => {
                position.push(path.lng, path.lat)
            })
            // console.log(position);
            renderLines(viewer, {
                positions: position,
                color: new Cesium.Color.fromCssColorString(color),
                name
            })
            // 渲染站点
            stationsList.forEach(station => {
                const { position, name } = station
                renderStation(viewer, {
                    positions: position,
                    name,
                    color
                }),
                    renderStationBill(viewer, {
                        positions: position,
                        name,
                        color,
                        attr: {
                            name: station.name,
                            isChange: 1 ? true : false,
                        }
                    })
            })
        })
    }
}

// 清除全部
export const removeAll = (viewer) => {
    removeAllLines(viewer)
    removeAllStations(viewer)
    removeAllBillboards()
}

const billboards = [];
// 渲染站点标牌，后期还要添加点击查询功能
export const renderStationBill = async (viewer, options) => {

    const positions = Cesium.defaultValue(options.positions, {
        lng: 0,
        lat: 0,
    });
    //   console.log(positions,'positions')
    const height = Cesium.defaultValue(options.height, 800);
    const name = Cesium.defaultValue(options.name, "站点");
    const show = Cesium.defaultValue(options.show, true);
    const color = Cesium.defaultValue(options.color, "#ff0000");
    const attr = Cesium.defaultValue(options.attr, {});
    const isCache = Cesium.defaultValue(options.isCache, true);
    const billControler = new SimpleLabel(
        viewer,
        {
            position: Cesium.Cartesian3.fromDegrees(positions.lng, positions.lat, height),
            label: name,
            isShow: show,
            color: color,
            scaleByDistance: new Cesium.NearFarScalar(1000, 1, 20000, 0.4),
            attr: attr,
            type: 'marker'
        }
    );
    await billControler.addLabel();

    const target = {
        billControler,
        billboard: billControler.vmInstance.el,
        name
    };
    isCache && billboards.push(target);
    return target;
};

// 清除所有站点标牌
export const removeAllBillboards = () => {
    billboards.forEach((item) => {
        const { billControler } = item;
        billControler.removeMarker();
        billControler.queryPopup && billControler.removeQueryPopup();
    });
};

// 根据名称Array控制站点标牌显示与隐藏
export const changeDisplayBillBoard = (names, isShow) => {
    const filterBills = billboards.filter(
        (item) => names.indexOf(item.billControler.label) > -1
    );
    filterBills.forEach((item) => {
        const { billboard, billControler } = item;
        billControler.isDisplay = isShow;
        billboard.style.display = isShow ? "block" : "none";
    });
};

// 通过名称整体控制显示隐藏
export const displayByName = (lineNames, stationNames, isShow) => {
    hideLineByName(lineNames, isShow)
    hideStationByName(stationNames, isShow)
    changeDisplayBillBoard(stationNames, isShow)
}

// 按照缓存数据清除
// cacheData类型 {
//   lineEnts:[],
//   stationEnts:[],
//   billboards:[{
//     billControler:SimpleLabel实例,
//     billboard:Billboard实例
//}]
// }
export const removeByCacheData = (viewer, cacheData) => {
    if (Object.keys(cacheData).length === 0) {
        return
    }
    const { lineEnts, stationEnts, billboards } = cacheData;
    if (lineEnts?.length > 0) {
        lineEnts.forEach(line => viewer.entities.remove(line))
        stationEnts.forEach(station => {
            const { conePrimitve, bottomCircleEntity } = station;
            viewer.scene.primitives.remove(conePrimitve);
            viewer.entities.remove(bottomCircleEntity);
        })
        billboards.forEach((item) => {
            const { billControler } = item;
            billControler.removeMarker();
            billControler.removeQueryPopup();
        });
    }

}

// 视角飞到全局
export const flyToDefaultView = (viewer) => {
    viewer.camera.flyTo({
        destination: Cesium.Cartesian3.fromDegrees(113.95, 30.19, 34000),
        duration: 2,
        orientation: {
            heading: Cesium.Math.toRadians(35.0),
            pitch: Cesium.Math.toRadians(-37.0),
            roll: 0.0,
        },
    });
};

// 通过名称找到对应的站点，站牌
export const findyBillboardByName = (name, cacheData) => {
    let billboardsData = billboards
    let stationsData = stations
    // 使用自己的缓存数据
    if (cacheData) {
        const { billboards, stationEnts } = cacheData
        billboardsData = billboards
        stationsData = stationEnts
    }
    const targetBillboard = billboardsData.find((item) => item.billControler.label === name);
    const stationEnt = stationsData.find((item) => item.name === name);
    return {
        billboard: targetBillboard,
        station: stationEnt,
    }
}

let lastFocusStation
// 聚焦到站点并展示查询信息
export const focusOnStation = (viewer, name, cacheData) => {
    const target = findyBillboardByName(name, cacheData);
    console.log(lastFocusStation,'lastFocusStation',target, name, cacheData)
    const { billboard: { billControler }, station } = target
    if (lastFocusStation) {
       
        const { billControler } = lastFocusStation  
        billControler.removeQueryPopup()
    }

    if (station && billControler) {
        const { bottomCircleEntity } = station
        viewer.flyTo(bottomCircleEntity, {
            offset: new Cesium.HeadingPitchRange(Cesium.Math.toRadians(40), Cesium.Math.toRadians(-40), 5000)
        });
        // 调用billControler的showQueryPopup方法
        billControler.showQueryPopup()
        lastFocusStation = target.billboard
    }
}
